package com.example.controller;

import java.io.IOException;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.Resource;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.servlet.support.ServletUriComponentsBuilder;

import com.example.dto.ApiResponse;
import com.example.service.FileStorageService;
import com.example.service.UserService;

import jakarta.servlet.ServletContext;
import jakarta.servlet.http.HttpServletRequest;

@RestController
@RequestMapping("/api/files")
public class FileController {

    @Autowired
    private FileStorageService fileStorageService;

    @Autowired
    private UserService userService;

    @Autowired
    private ServletContext servletContext;

    /**
     * 上传文件接口
     * 该接口用于处理文件上传请求，将文件存储到服务器，并返回文件的下载链接。
     *
     * @param file 要上传的文件，类型为MultipartFile
     * @return 返回ApiResponse对象，包含操作是否成功、成功消息和文件下载链接
     */
    @PostMapping("/upload")
    public ApiResponse uploadFile(@RequestParam("file") MultipartFile file) {
        String fileName = fileStorageService.storeFile(file, null);

        String fileDownloadUri = ServletUriComponentsBuilder.fromCurrentContextPath()
                .path("/api/files/download/")
                .path(fileName)
                .toUriString();

        return new ApiResponse(true, "File uploaded successfully",
                             fileDownloadUri);
    }

    /**
     * 上传多个文件
     * 该接口接收多个文件并依次上传，返回每个文件的上传结果
     *
     * @param files 要上传的文件数组
     * @return 每个文件的上传结果列表
     */
    @PostMapping("/uploadMultiple")
    public List<ApiResponse> uploadMultipleFiles(@RequestParam("files") MultipartFile[] files) {
        return Arrays.stream(files)
                .map(this::uploadFile)
                .collect(Collectors.toList());
    }

    /**
     * 上传用户头像
     * 该接口用于处理用户上传头像的请求，包括文件存储、更新用户头像URL以及删除旧头像文件。
     *
     * @param file 用户上传的头像文件
     * @return 如果上传成功，返回包含成功信息和头像URL的响应；如果失败，返回错误信息
     * @throws Exception 上传过程中发生异常时抛出
     */
    @PostMapping("/avatar")
    public ResponseEntity<?> uploadAvatar(@RequestParam("file") MultipartFile file) {
        try {
            // 获取当前用户ID
            Long currentUserId = userService.getCurrentUserId();
            if (currentUserId == null) {
                return ResponseEntity.badRequest().body(new ApiResponse(false, "User not authenticated", null));
            }
            
            // 获取用户当前的头像URL，用于稍后删除旧文件
            String currentAvatarUrl = userService.getUserAvatarUrl(currentUserId);
            
            // 将头像文件存储在 avatars 子文件夹中
            String fileName = fileStorageService.storeFile(file, "avatars");

            // 构建头像访问路径（与前端路径保持一致）
            String avatarUrl = "/users/avatars/" + fileName.replace("avatars/", "");

            // 更新用户头像URL（存储相对路径）
            ApiResponse response = userService.updateAvatar(currentUserId, avatarUrl);

            if (response.isSuccess()) {
                // 成功更新头像后，删除旧的头像文件（如果存在）
                if (currentAvatarUrl != null && !currentAvatarUrl.isEmpty() 
                        && !currentAvatarUrl.equals("/users/avatars/default-avatar.png")) {
                    fileStorageService.deleteFile(currentAvatarUrl);
                }
                
                return ResponseEntity.ok(new ApiResponse(true, "Avatar updated successfully", avatarUrl));
            } else {
                return ResponseEntity.badRequest().body(response);
            }
        } catch (Exception e) {
            return ResponseEntity.badRequest()
                    .body(new ApiResponse(false, "Could not upload avatar: " + e.getMessage(), null));
        }
    }

    /**
     * 下载文件
     * 该接口用于下载指定文件名的文件，并返回文件资源。
     *
     * @param fileName 要下载的文件名
     * @param request  HttpServletRequest对象，用于获取ServletContext
     * @return 如果文件存在，返回包含文件资源信息的ResponseEntity；如果文件不存在，返回404错误
     */
    @GetMapping("/download/{fileName:.+}")
    public ResponseEntity<Resource> downloadFile(@PathVariable String fileName,
                                               HttpServletRequest request) {
        try {
            Resource resource = fileStorageService.loadFileAsResource(fileName);

            String contentType = null;
            try {
                contentType = request.getServletContext().getMimeType(resource.getFile().getAbsolutePath());
            } catch (IOException ex) {
                contentType = "application/octet-stream";
            }

            return ResponseEntity.ok()
                    .contentType(MediaType.parseMediaType(contentType))
                    .header(HttpHeaders.CONTENT_DISPOSITION,
                            "attachment; filename=\"" + resource.getFilename() + "\"")
                    .body(resource);
        } catch (Exception e) {
            return ResponseEntity.notFound().build();
        }
    }
}